package com.spontaneappnew.activities;

import java.util.List;
import com.parse.FindCallback;
import com.parse.GetCallback;
import com.parse.Parse;
import com.parse.ParseException;
import com.parse.ParseObject;
import com.parse.ParseQuery;
import com.parse.SaveCallback;
import com.spontaneappnew.R;
import android.os.Bundle;
import android.app.Activity;
import android.app.AlertDialog;
import android.app.ProgressDialog;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.SharedPreferences;
import android.view.Menu;
import android.view.MenuItem;
import android.widget.EditText;
import android.widget.RatingBar;
import android.widget.TextView;
import android.widget.Toast;

public class RateAndCommentPlaceActivity extends Activity {
	
	private TextView placeNameTextView;
	private EditText commentEditText;
	private RatingBar ratingBar;
	private ProgressDialog mProgressDialog;
	
	private String placeName, placeId;
	private ParseObject currPlace;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_rate_and_comment_place);
		
		mProgressDialog = new ProgressDialog(this);
		// let the user know things are happening in the background while we get the place from server
		showProgressCircle();

		Parse.initialize(RateAndCommentPlaceActivity.this,
				"OHKt17cGZqBhJEdOcHDQW771ZhUQgTrkd3IAWrRk", "IckQgfToDOtil3LEf586QW3bDLeAVa7PE8SWaxU6");
		
		placeNameTextView = (TextView)findViewById(R.id.rate_and_comment_place_name_textView);
		commentEditText = (EditText)findViewById(R.id.rate_and_comment_place_editText);
		ratingBar = (RatingBar)findViewById(R.id.rate_and_comment_place_ratingBar);
		Intent intent = getIntent();
		placeId = intent.getStringExtra("placeId");
		placeName = intent.getStringExtra("placeName");
		placeNameTextView.setText(placeName);	
		getPlaceFromServer();
		
	}

	@Override
	public boolean onCreateOptionsMenu(Menu menu) {
		// Inflate the menu; this adds items to the action bar if it is present.
		getMenuInflater().inflate(R.menu.rate_and_comment_place, menu);
		
		return true;
	}
	
	@Override
	public boolean onOptionsItemSelected(MenuItem item) {
		// user pressed the done button
		if(item.getItemId() == R.id.action_rate_and_comment_place_done){
			// Check that we got the place from the server and then validate use 
			if(currPlace != null){
				hideProgressCircle();
				validateUserInput();
			// There's been a problem getting the place from the server, try again
			} else {
				showProgressCircle();
				getPlaceFromServer();
				Toast.makeText(this, "Waiting for server communication please wait", 
						Toast.LENGTH_SHORT).show();
			}
			return true;
		// user pressed the cancel button
		} else if(item.getItemId() == R.id.action_rate_and_comment_place_cancel){
			showAreYouSureDialog();
			return true;
		// user pressed the reload button
		} else if(item.getItemId() == R.id.action_rate_and_comment_place_reload){
			// let the user know things are happening in the background while we get the place from server
			showProgressCircle();
			getPlaceFromServer();
			return true;
		}
		else{
			return super.onOptionsItemSelected(item);			
		}
	}

	private void validateUserInput() {
		final String comment = commentEditText.getText().toString();
		final float rating = ratingBar.getRating();
		// If any of the fields are not valid - pop dialog to ask the user to 
    	// fix it and then retry
    	String msg = "";
    	boolean isValidComment = !(comment == null || comment.length() == 0);
    	boolean isRatingNotZero = !(rating == 0);
    	
    	if(!isValidComment && !isRatingNotZero){
    		msg = "You didn't leave any rating or commemt, " +
    				"if you hit \"Yes\" this place will get rating of 0, " +
    				"are you sure you want to continue?";
    	} else if(!isValidComment) {
    		msg = "Are you sure you don't want to leave a comment?";
    	} else if(!isRatingNotZero){
    		msg = "Are you sure you want to rate this place 0??";
    	} else{
    		addNewComment(comment, rating);
    		return;
    	}
    	// One of the fields are not valid, show dialog to confirm with the user
		AlertDialog.Builder builder = new AlertDialog.Builder(RateAndCommentPlaceActivity.this);
		builder.setMessage(msg)
		       .setCancelable(false)
		       .setPositiveButton("Yes", new DialogInterface.OnClickListener() {
		           public void onClick(DialogInterface dialog, int id) {
		                dialog.dismiss();
		                addNewComment(comment, rating);
		                // finish the activity
		                finish();
		           }
		       })
		       .setNegativeButton("No", new DialogInterface.OnClickListener() {
		           public void onClick(DialogInterface dialog, int id) {
		                dialog.dismiss();
		           }
		       });
		AlertDialog alert = builder.create();
		alert.show();
		return;
	}
	
	private void addNewComment(String comment, final float rating) {
		Toast.makeText(RateAndCommentPlaceActivity.this, 
				"Thanks! See you soon and don't forget to be spontaneous!!", Toast.LENGTH_LONG).show();
		final ParseObject parseNewComment = new ParseObject("Comments");
		parseNewComment.put("comment", comment);
		parseNewComment.put("rating", rating);
		SharedPreferences pref = getSharedPreferences("PREF", 0);
		final String userID = pref.getString("FBID", "");
		parseNewComment.put("userID", userID);
		parseNewComment.put("placeID",currPlace.getString("name"));
		parseNewComment.saveInBackground(new SaveCallback() {
			
			@Override
			public void done(ParseException arg0) {
				String commentID = parseNewComment.getObjectId();		
				currPlace.add("comments", commentID);
				int numOfRatings = currPlace.getInt("numRatings")+1;
				currPlace.put("numRatings",numOfRatings);
				double totalRatings = currPlace.getDouble("SumOfRatings");
				totalRatings=totalRatings+(double)rating;
				currPlace.put("SumOfRatings", totalRatings);
				double newRating = totalRatings/numOfRatings;
				
				double integerPart = Math.floor(newRating);
				double fractionPart = newRating - integerPart;
				double fractionPartAfterRounding;
				if (fractionPart < 0.25){
					fractionPartAfterRounding=0;
				}
				else if (fractionPart < 0.75){
					fractionPartAfterRounding = 0.5;
				}
				else {
					fractionPartAfterRounding = 1.0;
				}
				newRating = integerPart + fractionPartAfterRounding;
				currPlace.put("rating", newRating);
				currPlace.saveInBackground();
				//check if user entry exists and if so add to comments array if not create new
				//entry and add to comments array
				
				ParseQuery<ParseObject> query = new ParseQuery<ParseObject>("User_History").whereEqualTo("userID", userID);
				query.findInBackground(new FindCallback<ParseObject>() {
					
					@Override
					public void done(List<ParseObject> user, ParseException arg1) {
						if (user.size()==0){
							ParseObject newUser = new ParseObject("User_History");
							newUser.add("comments", parseNewComment.getObjectId());
							newUser.saveInBackground();
						}
						else{
							user.get(0).add("comments", parseNewComment.getObjectId());
							user.get(0).saveInBackground();
						}
						
					}
				});			
				// finish the activity
                finish();
				
				
			}
		});
	}

	private void showAreYouSureDialog() {
		String msg = "This app is all about sharing! \n" +
				"We would really appreciate your input. " +
				"Are you sure you don't want to leave your comment and rating?";
		AlertDialog.Builder builder = new AlertDialog.Builder(RateAndCommentPlaceActivity.this);
		builder.setMessage(msg)
		       .setCancelable(true)
		       .setPositiveButton("I'm Sure", new DialogInterface.OnClickListener() {
		           public void onClick(DialogInterface dialog, int id) {
		                dialog.dismiss();
		                Toast.makeText(RateAndCommentPlaceActivity.this, "See you next time!\n" +
		                		"And don't forget to be spontaneous!", Toast.LENGTH_SHORT).show();
		                // finish the activity
		                finish();
		           }
		       })
		       .setNegativeButton("Go Back", new DialogInterface.OnClickListener() {
		           public void onClick(DialogInterface dialog, int id) {
		                dialog.dismiss();
		           }
		       });
		AlertDialog alert = builder.create();
		alert.show();
	}
	
	/*
	 * Get the place from the server according to the placeId so we can add the comments and rating 
	 */
	private void getPlaceFromServer() {
		ParseQuery<ParseObject> query = new ParseQuery<ParseObject>("Places");
		query.getInBackground(placeId, new GetCallback<ParseObject>() {
					
			@Override
			public void done(ParseObject place, ParseException arg1) {
				currPlace = place;
				hideProgressCircle();
			}
		});
	}

	
///////////////////// Progress Dialog Circle methods ///////////////////////////////
    
	// Sets up a progress dialog with a spinner to show when performing stuff in the background
	protected void showProgressCircle(){
		mProgressDialog.setMessage("Loading");
		mProgressDialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);
		mProgressDialog.setIndeterminate(true);
		mProgressDialog.show();
	}
	
	// Hides the progress dialog when done performing stuff in the background
	protected void hideProgressCircle(){
		mProgressDialog.hide();
	}

}
